package core;

/**
 * The GameAction class is used as a key-binding for mapping key events to a
 * response in the game engine.
 * 
 * @author Jason
 * 
 */
public class GameKeyAction {

	protected String name;

	protected int timesPressed;
	protected int timesReleased;
	protected boolean keyDown = false;
	protected boolean wasDown = false;

	/**
	 * Constructs a GameKeyAction with the specified name.
	 */
	public GameKeyAction(String actionName) {
		this.name = actionName;
	}

	/**
	 * Signifies that this key has been pressed.
	 */
	public synchronized void press() {
		timesPressed++;
		keyDown = true;
	}

	/**
	 * Signifies that this key has been released.
	 */
	public synchronized void release() {
		timesReleased++;
		keyDown = false;
	}

	/**
	 * @return Whether or not the button is in a different state (up or down)
	 *         since the isStateChanged() was called.
	 */
	public boolean isStateChanged() {
		boolean ret = (keyDown != wasDown);
		wasDown = keyDown;
		return ret;
	}

	/**
	 * Returns whether or not this key is pressed down.
	 */
	public boolean isKeyDown() {
		return keyDown;
	}

	/**
	 * This gets the number of times that this key was pressed down manually by
	 * the user. Calling this method resets the counter.
	 */
	public synchronized int getTimesTyped() {
		wasDown = keyDown;
		if (timesPressed == timesReleased)
			return timesReleased;
		return timesReleased + 1;
	}

	/**
	 * Gets the number of times that this key was pressed. Calling this method
	 * resets the counter.<br>
	 * <br>
	 * Note: If you hold the key down, most operating systems will generate many
	 * KeyPressed events. You may want to use getTimesTyped().
	 */
	public synchronized int getTimesPressed() {
		wasDown = keyDown;
		return timesPressed;
	}

	/**
	 * Resets the counters.
	 */
	public synchronized void reset() {
		timesPressed = 0;
		timesReleased = 0;
	}

	/**
	 * Gets the name of this key action.
	 */
	public String getName() {
		return name;
	}

}
